package org.soc.timesheet.domain;
import flexjson.JSONDeserializer;
import flexjson.JSONSerializer;

import java.util.Calendar;
import java.util.Collection;
import java.util.List;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EntityManager;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.PersistenceContext;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.TypedQuery;
import javax.validation.constraints.NotNull;

import org.apache.commons.lang3.builder.ReflectionToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import org.hibernate.annotations.GenericGenerator;
import org.springframework.beans.factory.annotation.Configurable;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.roo.addon.dbre.RooDbManaged;
import org.springframework.roo.addon.javabean.RooJavaBean;
import org.springframework.roo.addon.jpa.activerecord.RooJpaActiveRecord;
import org.springframework.roo.addon.json.RooJson;
import org.springframework.roo.addon.tostring.RooToString;
import org.springframework.transaction.annotation.Transactional;

@Configurable
@Entity
@Table(name = "USERS_LOGGED")
@RooJavaBean
@RooJpaActiveRecord(versionField = "", table = "USERS_LOGGED")
@RooDbManaged(automaticallyDelete = true)
@RooToString(excludeFields = { "idUser" })
@RooJson
public class UsersLogged {

	 public static Long countFindUsersLoggedsByTokenEquals(String token) {
	        if (token == null || token.length() == 0) throw new IllegalArgumentException("The token argument is required");
	        EntityManager em = UsersLogged.entityManager();
	        TypedQuery q = em.createQuery("SELECT COUNT(o) FROM UsersLogged AS o WHERE o.token = :token", Long.class);
	        q.setParameter("token", token);
	        return ((Long) q.getSingleResult());
	    }

	        public static TypedQuery<UsersLogged> findUsersLoggedsByTokenEquals(String token) {
	        if (token == null || token.length() == 0) throw new IllegalArgumentException("The token argument is required");
	        EntityManager em = UsersLogged.entityManager();
	        TypedQuery<UsersLogged> q = em.createQuery("SELECT o FROM UsersLogged AS o WHERE o.token = :token", UsersLogged.class);
	        q.setParameter("token", token);
	        return q;
	    }

	        public static TypedQuery<UsersLogged> findUsersLoggedsByTokenEquals(String token, String sortFieldName, String sortOrder) {
	        if (token == null || token.length() == 0) throw new IllegalArgumentException("The token argument is required");
	        EntityManager em = UsersLogged.entityManager();
	        StringBuilder queryBuilder = new StringBuilder("SELECT o FROM UsersLogged AS o WHERE o.token = :token");
	        if (fieldNames4OrderClauseFilter.contains(sortFieldName)) {
	            queryBuilder.append(" ORDER BY ").append(sortFieldName);
	            if ("ASC".equalsIgnoreCase(sortOrder) || "DESC".equalsIgnoreCase(sortOrder)) {
	                queryBuilder.append(" ").append(sortOrder);
	            }
	        }
	        TypedQuery<UsersLogged> q = em.createQuery(queryBuilder.toString(), UsersLogged.class);
	        q.setParameter("token", token);
	        return q;
	    }


	public String toString() {
        return new ReflectionToStringBuilder(this, ToStringStyle.SHORT_PREFIX_STYLE).setExcludeFieldNames("idUser").toString();
    }

	@PersistenceContext
    transient EntityManager entityManager;

	public static final List<String> fieldNames4OrderClauseFilter = java.util.Arrays.asList("");

	public static final EntityManager entityManager() {
        EntityManager em = new UsersLogged().entityManager;
        if (em == null) throw new IllegalStateException("Entity manager has not been injected (is the Spring Aspects JAR configured as an AJC/AJDT aspects library?)");
        return em;
    }

	public static long countUsersLoggeds() {
        return entityManager().createQuery("SELECT COUNT(o) FROM UsersLogged o", Long.class).getSingleResult();
    }

	public static List<UsersLogged> findAllUsersLoggeds() {
        return entityManager().createQuery("SELECT o FROM UsersLogged o", UsersLogged.class).getResultList();
    }

	public static List<UsersLogged> findAllUsersLoggeds(String sortFieldName, String sortOrder) {
        String jpaQuery = "SELECT o FROM UsersLogged o";
        if (fieldNames4OrderClauseFilter.contains(sortFieldName)) {
            jpaQuery = jpaQuery + " ORDER BY " + sortFieldName;
            if ("ASC".equalsIgnoreCase(sortOrder) || "DESC".equalsIgnoreCase(sortOrder)) {
                jpaQuery = jpaQuery + " " + sortOrder;
            }
        }
        return entityManager().createQuery(jpaQuery, UsersLogged.class).getResultList();
    }

	public static UsersLogged findUsersLogged(String id) {
        if (id == null || id.length() == 0) return null;
        return entityManager().find(UsersLogged.class, id);
    }

	public static List<UsersLogged> findUsersLoggedEntries(int firstResult, int maxResults) {
        return entityManager().createQuery("SELECT o FROM UsersLogged o", UsersLogged.class).setFirstResult(firstResult).setMaxResults(maxResults).getResultList();
    }

	public static List<UsersLogged> findUsersLoggedEntries(int firstResult, int maxResults, String sortFieldName, String sortOrder) {
        String jpaQuery = "SELECT o FROM UsersLogged o";
        if (fieldNames4OrderClauseFilter.contains(sortFieldName)) {
            jpaQuery = jpaQuery + " ORDER BY " + sortFieldName;
            if ("ASC".equalsIgnoreCase(sortOrder) || "DESC".equalsIgnoreCase(sortOrder)) {
                jpaQuery = jpaQuery + " " + sortOrder;
            }
        }
        return entityManager().createQuery(jpaQuery, UsersLogged.class).setFirstResult(firstResult).setMaxResults(maxResults).getResultList();
    }

	@Transactional
    public void persist() {
        if (this.entityManager == null) this.entityManager = entityManager();
        this.entityManager.persist(this);
    }

	@Transactional
    public void remove() {
        if (this.entityManager == null) this.entityManager = entityManager();
        if (this.entityManager.contains(this)) {
            this.entityManager.remove(this);
        } else {
            UsersLogged attached = UsersLogged.findUsersLogged(this.id);
            this.entityManager.remove(attached);
        }
    }

	@Transactional
    public void flush() {
        if (this.entityManager == null) this.entityManager = entityManager();
        this.entityManager.flush();
    }

	@Transactional
    public void clear() {
        if (this.entityManager == null) this.entityManager = entityManager();
        this.entityManager.clear();
    }

	@Transactional
    public UsersLogged merge() {
        if (this.entityManager == null) this.entityManager = entityManager();
        UsersLogged merged = this.entityManager.merge(this);
        this.entityManager.flush();
        return merged;
    }

	@ManyToOne
    @JoinColumn(name = "ID_USER", referencedColumnName = "ID", nullable = false)
    private Users idUser;

	@Column(name = "LAST_REQUEST", length = 500)
    private String lastRequest;

	@Column(name = "LAST_ACCESS")
    @NotNull
    @Temporal(TemporalType.TIMESTAMP)
    @DateTimeFormat(style = "MM")
    private Calendar lastAccess;

	@Column(name = "TOKEN", length = 200, unique = true)
    @NotNull
    private String token;

	@Column(name = "SESSIO_ID", length = 200)
    @NotNull
    private String sessioId;

	@Column(name = "REFERER", length = 45)
    private String referer;

	@Column(name = "ID_TOKEN_TYPE")
    @NotNull
    private Integer idTokenType;

	public Users getIdUser() {
        return idUser;
    }

	public void setIdUser(Users idUser) {
        this.idUser = idUser;
    }

	public String getLastRequest() {
        return lastRequest;
    }

	public void setLastRequest(String lastRequest) {
        this.lastRequest = lastRequest;
    }

	public Calendar getLastAccess() {
        return lastAccess;
    }

	public void setLastAccess(Calendar lastAccess) {
        this.lastAccess = lastAccess;
    }

	public String getToken() {
        return token;
    }

	public void setToken(String token) {
        this.token = token;
    }

	public String getSessioId() {
        return sessioId;
    }

	public void setSessioId(String sessioId) {
        this.sessioId = sessioId;
    }

	public String getReferer() {
        return referer;
    }

	public void setReferer(String referer) {
        this.referer = referer;
    }

	public Integer getIdTokenType() {
        return idTokenType;
    }

	public void setIdTokenType(Integer idTokenType) {
        this.idTokenType = idTokenType;
    }

	@Id
    @GeneratedValue(generator = "alphanumeric")
    @GenericGenerator(name = "alphanumeric", strategy = "org.soc.timesheet.custom.domain.generators.RandomStringIdGenerator", parameters = { @org.hibernate.annotations.Parameter(name = "length", value = "100") })
    @Column(name = "ID", length = 100)
    private String id;

	public String getId() {
        return this.id;
    }

	public void setId(String id) {
        this.id = id;
    }

	public String toJson() {
        return new JSONSerializer()
        .exclude("*.class").serialize(this);
    }

	public String toJson(String[] fields) {
        return new JSONSerializer()
        .include(fields).exclude("*.class").serialize(this);
    }

	public static UsersLogged fromJsonToUsersLogged(String json) {
        return new JSONDeserializer<UsersLogged>()
        .use(null, UsersLogged.class).deserialize(json);
    }

	public static String toJsonArray(Collection<UsersLogged> collection) {
        return new JSONSerializer()
        .exclude("*.class").serialize(collection);
    }

	public static String toJsonArray(Collection<UsersLogged> collection, String[] fields) {
        return new JSONSerializer()
        .include(fields).exclude("*.class").serialize(collection);
    }

	public static Collection<UsersLogged> fromJsonArrayToUsersLoggeds(String json) {
        return new JSONDeserializer<List<UsersLogged>>()
        .use("values", UsersLogged.class).deserialize(json);
    }
}
